from django.conf import settings
from django.contrib.auth.decorators import login_required
from django.core.urlresolvers import reverse, reverse_lazy
from django.http import Http404, HttpResponseRedirect, HttpResponse
from django.shortcuts import render_to_response
from django.template import RequestContext
from django.utils import simplejson
from django.utils.http import urlquote

from relationships.decorators import require_owner, require_owner_list
from relationships.models import RelationshipStatus, Relationship

from django.views.generic.list import ListView
from django.utils.decorators import method_decorator
from django.shortcuts import get_object_or_404
from django.contrib.auth.models import User
from django.views.generic.edit import CreateView, UpdateView, DeleteView
from relationships import forms as relationships_forms
from django.db.models import Count
from django.db import transaction

    
def RelationshipsAjax(request):
    if request.method == 'GET':
        
        to_user_id = request.GET['to_user']
        from_user_id = request.GET['from_user']
        status_id = request.GET['status']
        
        # Save data in db
        relations = Relationship(to_user_id=to_user_id, from_user_id=from_user_id, status_id=status_id)
        new_relations = relations.save()
        
        # Return Output
        # data = simplejson.dumps({"status":"<li>success</li>", "error":"error", "data":request.POST})
        r = Relationship.objects.filter(status__id=status_id)
        return render_to_response('relationships/relation_ajax_list.html', {'form': r }, context_instance=RequestContext(request))


# update Relationship Status
class RelationshipStatusUpdate(UpdateView):
    model = RelationshipStatus
    # view_name.class_name
    form_class  = relationships_forms.RelationshipStatusForm
    template_name = "relationships/relationshipstatus_add.html"
    
    @method_decorator(login_required)
    #@method_decorator(require_owner)
    def dispatch(self, *args, **kwargs):
        return super(RelationshipStatusUpdate, self).dispatch(*args, **kwargs)
    
    # Success Process to url ...
    def get_success_url(self):
        return reverse('relationshipstatus_list')

class RelationshipStatusAdd(CreateView):
    model = RelationshipStatus
    form_class  = relationships_forms.RelationshipStatusForm
    template_name = "relationships/relationshipstatus_add.html"
    
    @method_decorator(login_required)
    def dispatch(self, *args, **kwargs):
        return super(RelationshipStatusAdd, self).dispatch(*args, **kwargs)
    
    # default value in object <owner>
    def get_initial(self):
        initial = dict()
        initial['owner'] = User.objects.get(username=self.request.user.username)
        return initial
    
    def get_success_url(self):
        return reverse('relationshipstatus_list')

@login_required
def relationshipstatus_redirect(request):
    return HttpResponseRedirect(reverse('relationshipstatus_list', args=[request.user.username]))

class RelationshipStatusListView(ListView):
    '''
    List all RelationshipStatus for requested user
    '''
    context_object_name='relationshipstatus_list'
    page=1
    paginate_by=50
    template_name='relationships/relationshipstatus_list.html'
    extra_context=None

    @method_decorator(login_required)
    #@method_decorator(require_owner_list)
    def dispatch(self, *args, **kwargs):
        return super(RelationshipStatusListView, self).dispatch(*args, **kwargs)
    
    def get_context_data(self, **kwargs):
        # Call the base implementation first to get a context
        context = super(RelationshipStatusListView, self).get_context_data(**kwargs)
        
        if not self.extra_context: self.extra_context = dict()
        context['page'] = self.page
        context['paginate_by'] = self.paginate_by
        user = get_object_or_404(User, username__iexact=self.request.user.username)
        context['to_user_status'] = RelationshipStatus.objects.filter(relationship__to_user=user).annotate(member_count=Count('relationship'))
        context['request'] = self.request
        context['extra_context'] = self.extra_context

        return context

    def get_queryset(self):
        # get user from request object
        user = get_object_or_404(User,
                             username__iexact=self.request.user.username)
        # get relationshipshipStatus owned by user
        queryset = RelationshipStatus.objects.own_by_user(user)
        return queryset

class RelationshipStatusDelete(DeleteView):
    """
        Delete All Relationship in DB table relationships_relationship & relationships_relationshipstatus
    """
    
    context_object_name='this_status'
    model = RelationshipStatus
    success_url = reverse_lazy('relationshipstatus_list')
    template_name = "relationshipstatus_confirm_delete.html"
    
    @method_decorator(login_required)
    #@method_decorator(require_owner)
    def dispatch(self, *args, **kwargs):
        return super(RelationshipStatusDelete, self).dispatch(*args, **kwargs)
    
    def get_context_data(self, **kwargs):
        context = super(RelationshipStatusDelete, self).get_context_data(**kwargs)
        context['request'] = self.request
        # if empty query Relationship
        try:
            context['relationships'] = Relationship.objects.filter(status__id=self.kwargs['pk'])
        except:
            context['relationship'] = None

        return context
    
@login_required
def relationship_redirect(request):
    return HttpResponseRedirect(reverse('relationship_list', args=[request.user.username, status_slug]))

class RelationshipListView(ListView):
    '''
    List all Relationship for each RelationshipStatus with in requested user 
    '''
    context_object_name='user_list'
    page=1
    paginate_by=50
    template_name='relationships/relationship_list.html'
    extra_context=None

    @method_decorator(login_required)
    def dispatch(self, *args, **kwargs):
        return super(RelationshipListView, self).dispatch(*args, **kwargs)
    
    def get_context_data(self, **kwargs):
        # Call the base implementation first to get a context
        context = super(RelationshipListView, self).get_context_data(**kwargs)
        
        if not self.extra_context: self.extra_context = dict()
        context['page'] = self.page
        context['paginate_by'] = self.paginate_by
        context['request'] = self.request
        context['relation_status'] = get_object_or_404(RelationshipStatus, name=self.kwargs['status_slug'])
        status = RelationshipStatus.objects.get(name=self.kwargs['status_slug'])
        users = User.objects.exclude(id = self.request.user.id)
        context['user_non_relations'] = users.exclude(to_users_relationship__status=status)
        context['extra_context'] = self.extra_context

        return context

    def get_queryset(self):
        # get relationshipship for specific status
        status = get_object_or_404(RelationshipStatus, name=self.kwargs['status_slug'])
        queryset = Relationship.objects.filter(status=status)
        return queryset
    
class RelationshipsAdd(CreateView):
    model = Relationship
    form_class  = relationships_forms.RelationshipForm
    template_name = "relationships/relationship_add.html"
    
    @method_decorator(login_required)
    def dispatch(self, *args, **kwargs):
        return super(RelationshipsAdd, self).dispatch(*args, **kwargs)
    
    # default value in object <owner>
    def get_initial(self):
        initial = dict()
        initial['from_user'] = User.objects.get(username=self.request.user.username)
        initial['status'] = self.kwargs['status_id']
        return initial
    
    def get_success_url(self):
        status_slug = RelationshipStatus.objects.get(id=self.kwargs['status_id'])
        return reverse('relationship_list', args=(status_slug.name,))
    
class RelationshipsDelete(DeleteView):
    """
        Delete Relationship in DB table relationships_relationship
    """
    
    context_object_name='relation'
    model = Relationship
    #success_url = reverse_lazy('relationship_list', args=('New2',))
    template_name = "relationship_confirm_delete.html"
    
    @method_decorator(login_required)
    def dispatch(self, *args, **kwargs):
        return super(RelationshipsDelete, self).dispatch(*args, **kwargs)
    
    def get_context_data(self, **kwargs):
        context = super(RelationshipsDelete, self).get_context_data(**kwargs)
        context['request'] = self.request
        """
        # if empty query Relationship
        try:
            context['relationships'] = Relationship.objects.filter(id=self.kwargs['relation_id'])
        except:
            context['relationship'] = None
        """
        return context
    
    def get_success_url(self):
        return reverse('relationship_list', args=(self.kwargs['status_slug'],))
    
class RelationshipListToUserView(ListView):
    '''
    List all Relationship for each RelationshipStatus with in requested user 
    '''
    context_object_name='user_list'
    page=1
    paginate_by=50
    template_name='relationships/relationship_to_user_list.html'
    extra_context=None

    @method_decorator(login_required)
    def dispatch(self, *args, **kwargs):
        return super(RelationshipListToUserView, self).dispatch(*args, **kwargs)
    
    def get_context_data(self, **kwargs):
        # Call the base implementation first to get a context
        context = super(RelationshipListToUserView, self).get_context_data(**kwargs)
        
        if not self.extra_context: self.extra_context = dict()
        context['page'] = self.page
        context['paginate_by'] = self.paginate_by
        context['request'] = self.request
        context['relation_status'] = get_object_or_404(RelationshipStatus, name=self.kwargs['status_slug'])
        #status = RelationshipStatus.objects.get(name=self.kwargs['status_slug'])
        #context['relation'] = Relationship.objects.filter(status=status)
        context['extra_context'] = self.extra_context

        return context

    def get_queryset(self):
        # get relationshipship for specific status
        status = get_object_or_404(RelationshipStatus, name=self.kwargs['status_slug'])
        # get user from request object
        user = get_object_or_404(User,
                             username__iexact=self.request.user.username)
        queryset = user.relationships.get_related_to(status)
        return queryset
    
